package model

import (
	"context"
	"fmt"
	sq "github.com/Masterminds/squirrel"
	"github.com/zeromicro/go-zero/core/stores/cache"
	"github.com/zeromicro/go-zero/core/stores/sqlx"
	"xialou_platform/app/requestx"
)

var _ WalletWithdrawalModel = (*customWalletWithdrawalModel)(nil)

type (
	// WalletWithdrawalModel is an interface to be customized, add more methods here,
	// and implement the added methods in customWalletWithdrawalModel.
	WalletWithdrawalModel interface {
		walletWithdrawalModel
		FindListCount(ctx context.Context, keyword string, Type, status int64) int64
		FindList(ctx context.Context, page *requestx.ListReq, Type, status int64) ([]*WalletWithdrawal, error)
	}

	customWalletWithdrawalModel struct {
		*defaultWalletWithdrawalModel
	}
)

// NewWalletWithdrawalModel returns a model for the database table.
func NewWalletWithdrawalModel(conn sqlx.SqlConn, c cache.CacheConf) WalletWithdrawalModel {
	return &customWalletWithdrawalModel{
		defaultWalletWithdrawalModel: newWalletWithdrawalModel(conn, c),
	}
}

func (m *defaultWalletWithdrawalModel) FindListCount(ctx context.Context, keyword string, Type, status int64) int64 {
	selectBuilder := sq.Select("count(1)").From(m.table)
	if len(keyword) != 0 {
		selectBuilder = selectBuilder.LeftJoin("agent on agent.id = wallet_withdrawal.source_id")
		selectBuilder = selectBuilder.LeftJoin("store on store.id = wallet_withdrawal.source_id")
		selectBuilder = selectBuilder.Where(sq.Or{sq.Like{"agent.phone": fmt.Sprint("%", keyword, "%")}, sq.Like{"store.store_phone": fmt.Sprint("%", keyword, "%")}})
	}
	if Type > -1 {
		selectBuilder = selectBuilder.LeftJoin("wallet on wallet.id = wallet_withdrawal.wallet_id").Where(sq.Eq{"wallet.source_type": Type})
	}
	if status > -1 {
		selectBuilder = selectBuilder.Where(sq.Eq{"wallet_withdrawal.status": status})
	}
	query, args, err := selectBuilder.PlaceholderFormat(sq.Dollar).ToSql()
	if err != nil {
		return 0
	}
	var count int64
	err = m.QueryRowNoCacheCtx(ctx, &count, query, args...)
	if err != nil {
		return 0
	}
	return count

}

func (m *defaultWalletWithdrawalModel) FindList(ctx context.Context, page *requestx.ListReq, Type, status int64) ([]*WalletWithdrawal, error) {
	selectBuilder := sq.Select(" wallet_withdrawal.id,wallet_id,wallet_withdrawal.source_id,amount,wallet_withdrawal.balance,wallet_withdrawal.status,wallet_withdrawal.create_time,wallet_withdrawal.update_time,wallet_withdrawal.update_by,remark").From(m.table).Limit(page.Limit()).Offset(page.Offset())
	if len(page.Keyword) != 0 {
		selectBuilder = selectBuilder.LeftJoin("agent on agent.id = wallet_withdrawal.source_id")
		selectBuilder = selectBuilder.LeftJoin("store on store.id = wallet_withdrawal.source_id")
		selectBuilder = selectBuilder.Where(sq.Or{sq.Like{"agent.phone": fmt.Sprint("%", page.Keyword, "%")}, sq.Like{"store.store_phone": fmt.Sprint("%", page.Keyword, "%")}})
	}
	if Type > -1 {
		selectBuilder = selectBuilder.LeftJoin("wallet on wallet.id = wallet_withdrawal.wallet_id").Where(sq.Eq{"wallet.source_type": Type})
	}
	if status > -1 {
		selectBuilder = selectBuilder.Where(sq.Eq{"wallet_withdrawal.status": status})
	}
	query, args, err := selectBuilder.OrderBy("wallet_withdrawal.create_time desc").PlaceholderFormat(sq.Dollar).ToSql()
	if err != nil {
		return nil, err
	}
	var resp []*WalletWithdrawal
	err = m.QueryRowsNoCacheCtx(ctx, &resp, query, args...)
	return resp, err
}
